﻿using System;
using System.Collections.Generic;
using Autodesk.Revit.DB;
using Autodesk.Revit.DB.Plumbing;
using Autodesk.Revit.UI;
using YArchitech.Revit;
using YArchitech.Revit.RevitExtension;

namespace YArchitech.HVAC
{
	public class HYPipeSlope
	{
		public HYPipeSlope(double slope, string startElevation)
		{
			this.slope = slope;
			this.startElevation = startElevation;
		}

		public void MovePipe(UIDocument uiDoc)
		{
			try
			{
				Document document = uiDoc.Document;
				PipeFilter selectionFilter = new PipeFilter();
				SearchBranch searchBranch = new SearchBranch(uiDoc);
				searchBranch.PickFirstElement(selectionFilter, "请选择起始排水管道");
				searchBranch.DoSearch();
				ElementNode listRoot = searchBranch.GetListRoot();
				List<ElementNode> list = new List<ElementNode>();
				this.GetAllElemNode(listRoot, ref list);
				int num = 0;
				foreach (ElementNode item in list)
				{
					this.GetPipeElevation(document, item, num);
					num++;
				}
			}
			catch (Exception ex)
			{
				ex.ToString();
			}
		}

		private void GetPipeElevation(Document doc, ElementNode item, int i)
		{
			Pipe pipe = item.Element as Pipe;
			if (pipe != null)
			{
				XYZ origin = item.ConnectorIn.Origin;
				XYZ origin2 = item.ConnectorOut.Origin;
				double num = pipe.GetParameter(BuiltInParameter.RBS_PIPE_SLOPE).AsDouble();
				double num2;
				if (num == 0.0)
				{
					num2 = pipe.get_Parameter(BuiltInParameter.CURVE_ELEM_LENGTH).AsDouble();
				}
				else
				{
					num2 = pipe.get_Parameter(BuiltInParameter.CURVE_ELEM_LENGTH).AsDouble() / Math.Sqrt(num * num + 1.0);
				}
				double num3 = this.slope * num2;
				LocationCurve locationCurve = pipe.Location as LocationCurve;
				Line curve = locationCurve.Curve as Line;
				if (i == 0 && this.startElevation != "")
				{
					double num4 = double.Parse(this.startElevation);
					this.newZ = num4 / 304.8 + num3;
					XYZ startPoint;
					XYZ endPoint;
					if (curve.GetEndPoint(0).IsAlmostEqualTo(origin))
					{
						startPoint = new XYZ(origin.X, origin.Y, num4 / 304.8);
						endPoint = new XYZ(origin2.X, origin2.Y, this.newZ);
					}
					else
					{
						startPoint = new XYZ(origin2.X, origin2.Y, this.newZ);
						endPoint = new XYZ(origin.X, origin.Y, num4 / 304.8);
					}
					Line curve2 = YJKLineEx.YJKGetBound(startPoint, endPoint);
					locationCurve.Curve = curve2;
				}
				else
				{
					this.newZ = origin.Z + num3;
					XYZ startPoint;
					XYZ endPoint;
					if (curve.GetEndPoint(0).IsAlmostEqualTo(origin))
					{
						startPoint = origin;
						endPoint = new XYZ(origin2.X, origin2.Y, this.newZ);
					}
					else
					{
						startPoint = new XYZ(origin2.X, origin2.Y, this.newZ);
						endPoint = origin;
					}
					Line curve2 = YJKLineEx.YJKGetBound(startPoint, endPoint);
					locationCurve.Curve = curve2;
				}
				ElementTransformUtils.MoveElement(doc, pipe.Id, new XYZ(1E-05, 1E-05, 1E-05));
				ElementTransformUtils.MoveElement(doc, pipe.Id, -1.0 * new XYZ(1E-05, 1E-05, 1E-05));
				return;
			}
			FamilyInstance familyInstance = item.Element as FamilyInstance;
			if (familyInstance != null && !familyInstance.Symbol.Family.Name.Contains("过渡件"))
			{
				LocationPoint locationPoint = item.Element.Location as LocationPoint;
				if (familyInstance.Symbol.Family.Name.Contains("P型"))
				{
					item.Element.Location.Move(new XYZ(0.0, 0.0, this.newZ - this.GetZVectorConnector(familyInstance).Origin.Z));
					return;
				}
				item.Element.Location.Move(new XYZ(0.0, 0.0, this.newZ - locationPoint.Point.Z));
			}
		}

		private Connector GetZVectorConnector(FamilyInstance fi)
		{
			List<Connector> elementAllConnector = YJKRevitTools.GetElementAllConnector(fi);
			Connector result = null;
			foreach (Connector connector in elementAllConnector)
			{
				if (!connector.CoordinateSystem.BasisZ.IsAlmostEqualTo(new XYZ(0.0, 0.0, 1.0)))
				{
					result = connector;
					break;
				}
			}
			return result;
		}

		private void GetAllElemNode(ElementNode eNode, ref List<ElementNode> listENode)
		{
			if (eNode == null)
			{
				return;
			}
			Pipe pipe = eNode.Element as Pipe;
			if (pipe != null)
			{
				Line curve = (pipe.Location as LocationCurve).Curve as Line;
				double num = pipe.get_Parameter(BuiltInParameter.CURVE_ELEM_LENGTH).AsDouble();
				XYZ hyendPoint = curve.GetEndPoint(0);
				XYZ hyendPoint2 = curve.GetEndPoint(1);
				if (Math.Abs(hyendPoint.Z - hyendPoint2.Z) >= num / 3.0)
				{
					return;
				}
				listENode.Add(eNode);
			}
			else
			{
				listENode.Add(eNode);
			}
			this.GetAllElemNode(eNode.Next, ref listENode);
			if (eNode.SubElementNode != null)
			{
				foreach (ElementNode eNode2 in eNode.SubElementNode)
				{
					this.GetAllElemNode(eNode2, ref listENode);
				}
			}
		}

		private double slope;

		private string startElevation = "";

		private double newZ;
	}
}
